package com.xinQing.blogme.service.impl;

import com.xinQing.blogme.conf.annotation.CachedFunc;
import com.xinQing.blogme.constant.CacheConstant;
import com.xinQing.blogme.entity.User;
import com.xinQing.blogme.service.UserService;
import com.xinQing.blogme.util.Check;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.data.redis.core.ValueOperations;
import org.springframework.security.crypto.password.PasswordEncoder;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import java.util.List;
import java.util.stream.Collectors;

/**
 * Created by null on 2017/7/31.
 */
@Service
@Transactional
public class UserServiceImpl extends BaseServiceImpl<User, String>  implements UserService {

    @Value("${spring.redis.cacheKeyPrefix.user.id}")
    private String cacheKeyPrefix;

    @Value("${spring.redis.cacheKeyPrefix.user.username}")
    private String cacheKeyPrefixOfUsername;

    @Autowired
    private PasswordEncoder passwordEncoder;

    @Override
    @Transactional
    @CachedFunc
    public User findByUsername(String username) {
        ValueOperations<String, String> opsForValue = getOpsForValue();
        String cachedId = opsForValue.get(cacheKeyPrefixOfUsername + username);
        if (Check.isEmpty(cachedId)) {
            User user = new User();
            user.setUsername(username);
            User one = selectOne(user);
            setToCache(one);
            // 设置缓存username -> id
            opsForValue.set(cacheKeyPrefixOfUsername + username, getCacheKeyPrefixOfId() + one.getId(),
                    CacheConstant.EXPIRE_TIME, CacheConstant.EXPIRE_TIME_UNIT);
            return one;
        }
        return getByCachedJSONString(opsForValue.get(cachedId));
    }

    @Override
    @Transactional
    public int insert(User user) {
        String encodePassword = passwordEncoder.encode(user.getPassword());
        user.setPassword(encodePassword);
        return super.insert(user);
    }

    @Override
    public int insertList(List<User> list) {
        List<User> encodeList = list.stream()
                .map(user -> {
                    String encodePassword = passwordEncoder.encode(user.getPassword());
                    user.setPassword(encodePassword);
                    return user;
                }).collect(Collectors.toList());
        return super.insertList(encodeList);
    }

    @Override
    public String getCacheKeyPrefixOfId() {
        return cacheKeyPrefix;
    }

}